package com.example.demo0

import com.example.util.p

sealed class WaterMachineState(open val machine:WaterMachine){

    fun turnHeating(){

        if(this !is Heating){
            p("turn heating")
            this.machine.state = machine.heating
        }else{
            p("The state is already heating mode.")
        }

    }

    fun turnCooling(){
        if(this !is Cooling){
            p("turn cooling")
            machine.state = machine.cooling
        }else{
            p("The state is already cooling mode.")

        }
    }

    fun turnOff(){
        if(this !is Off){
            p("turn off")
            machine.state = machine.off

        }else{
            p("The state is already off")
        }
    }


}

class Off(override val machine:WaterMachine): WaterMachineState(machine)
class Heating(override val machine:WaterMachine): WaterMachineState(machine)
class Cooling(override val machine:WaterMachine): WaterMachineState(machine)



class WaterMachine{
    var state:WaterMachineState
    val off = Off(this)
    val heating = Heating(this)
    val cooling = Cooling(this)


    init {
        this.state = off
    }

    fun turnHeating(){
        this.state.turnHeating()
    }

    fun turnCooling(){
        this.state.turnCooling()
    }

    fun turnOff(){
        this.state.turnOff()
    }

}


enum class Moment{
    EARLY_MORNING,
    DRINKING_WATER,
    INSTANCE_NOODLES,
    AFTER_WORK

}

fun waterMachineOps(machine: WaterMachine,moment: Moment){
    when(moment){
        Moment.EARLY_MORNING,
        Moment.DRINKING_WATER->when(machine.state){
                !is Cooling -> machine.turnCooling()
            else -> {}
        }
        Moment.INSTANCE_NOODLES -> when(machine.state){
            !is Heating -> machine.turnHeating()
            else -> {}
        }
        Moment.AFTER_WORK->when(machine.state){
            !is Off -> machine.turnOff()
            else -> {}
        }
    }
}


fun main(){
    val machine = WaterMachine()
    waterMachineOps(machine,Moment.DRINKING_WATER)
    waterMachineOps(machine,Moment.INSTANCE_NOODLES)
    waterMachineOps(machine,Moment.DRINKING_WATER)
    waterMachineOps(machine,Moment.AFTER_WORK)
}


